package springweb.config;

import java.util.HashMap;
import java.util.Map;

import org.apache.shiro.cache.CacheManager;
import org.apache.shiro.cache.ehcache.EhCache;
import org.apache.shiro.cache.ehcache.EhCacheManager;
import org.apache.shiro.spring.web.ShiroFilterFactoryBean;
import org.apache.shiro.web.mgt.DefaultWebSecurityManager;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.cache.ehcache.EhCacheManagerFactoryBean;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.core.io.ClassPathResource;



/**
 * TODO add description
 */
@Configuration
public class ShiroConfiguration {

    /**
     * 安全管理器
     */
    @Bean
    public DefaultWebSecurityManager securityManager(@Qualifier("cacheShiroManager")CacheManager cacheShiroManager) {
        DefaultWebSecurityManager securityManager = new DefaultWebSecurityManager();
        securityManager.setRealm(this.shiroDbRealm());
        securityManager.setCacheManager(cacheShiroManager);
//        securityManager.setRememberMeManager(rememberMeManager);
//        securityManager.setSessionManager(defaultWebSessionManager);
        return securityManager;
    }
//    @Bean
//    public DefaultHashService defaultHashService(){
//    	DefaultHashService defaultHashService = new DefaultHashService();
//    	defaultHashService.setHashAlgorithmName("MD5");
//    	
//    	return defaultHashService;
//    }

    /**
     * session管理器
     */
//    @Bean
//    public DefaultWebSessionManager defaultWebSessionManager(CacheManager cacheShiroManager) {
//        DefaultWebSessionManager sessionManager = new DefaultWebSessionManager();
//        sessionManager.setCacheManager(cacheShiroManager);
//        sessionManager.setDeleteInvalidSessions(true);
//        sessionManager.setSessionValidationSchedulerEnabled(true);
//        Cookie cookie = new SimpleCookie(ShiroHttpSession.DEFAULT_SESSION_ID_NAME);
//        cookie.setName("shiroCookie");
//        cookie.setHttpOnly(true);
//        sessionManager.setSessionIdCookie(cookie);
//        return sessionManager;
//    }


    /**
     * 缓存管理器 使用Ehcache实现
     */
    @Bean(name="cacheShiroManager")
    public CacheManager getCacheShiroManager(EhCacheManagerFactoryBean ehCacheManagerFactoryBean) {
    	EhCacheManager cacheShiroManager = new EhCacheManager();
//    	cacheShiroManager.setCacheManager(ehcache.getObject());
//    	cacheShiroManager.set
//    	 cacheman
//    	net.sf.ehcache.management.CacheManager.c
    	cacheShiroManager.setCacheManager(ehCacheManagerFactoryBean.getObject());
//    	cacheShiroManager.setCacheManagerConfigFile("classpath:ehcache-shiro.xml");
//    	cacheShiroManager.setCacheManager(manager.getCacheManager());
        return cacheShiroManager;
    }
    
    @Bean
    public EhCacheManagerFactoryBean ehcache() {
        EhCacheManagerFactoryBean ehCacheManagerFactoryBean = new EhCacheManagerFactoryBean();
        ehCacheManagerFactoryBean.setConfigLocation(new ClassPathResource("ehcache-shiro.xml"));
        return ehCacheManagerFactoryBean;
    }

    /**
     * 项目自定义的Realm
     */
    @Bean
    public ShiroDbRealm shiroDbRealm() {
        return new ShiroDbRealm();
    }

    /**
     * rememberMe管理器, cipherKey生成见{@code Base64Test.java}
     */
//    @Bean
//    public CookieRememberMeManager rememberMeManager(SimpleCookie rememberMeCookie) {
//        CookieRememberMeManager manager = new CookieRememberMeManager();
//        manager.setCipherKey(Base64.decode("Z3VucwAAAAAAAAAAAAAAAA=="));
//        manager.setCookie(rememberMeCookie);
//        return manager;
//    }

    /**
     * 记住密码Cookie
     */
//    @Bean
//    public SimpleCookie rememberMeCookie() {
//        SimpleCookie simpleCookie = new SimpleCookie("rememberMe");
//        simpleCookie.setHttpOnly(true);
//        simpleCookie.setMaxAge(7 * 24 * 60 * 60);//7天
//        return simpleCookie;
//    }

    /**
     * Shiro的过滤器链
     */
    @Bean
    public ShiroFilterFactoryBean shiroFilter(DefaultWebSecurityManager securityManager) {
        ShiroFilterFactoryBean shiroFilter = new ShiroFilterFactoryBean();
        shiroFilter.setSecurityManager(securityManager);
        /**
         * 默认的登陆访问url
         */
        shiroFilter.setLoginUrl("/login");
        /**
         * 登陆成功后跳转的url
         */
        shiroFilter.setSuccessUrl("/index");
        /**
         * 没有权限跳转的url
         */
        shiroFilter.setUnauthorizedUrl("/global/error");
        
        /**
         * 配置shiro拦截器链
         *
         * anon  不需要认证
         * authc 需要认证
         * user  验证通过或RememberMe登录的都可以
         *
         */
        Map<String, String> hashMap = new HashMap<String, String>();
        hashMap.put("/static/**", "anon");
        hashMap.put("/templates/**", "anon");
        hashMap.put("/login", "anon");
//        hashMap.put("/global/sessionError", "anon");
//        hashMap.put("/kaptcha", "anon");
        hashMap.put("/tradetype/**", "anon");
        
        hashMap.put("/**", "authc");
        shiroFilter.setFilterChainDefinitionMap(hashMap);
        return shiroFilter;
    }

    /**
     * 在方法中 注入 securityManager,进行代理控制
     */
//    @Bean
//    public MethodInvokingFactoryBean methodInvokingFactoryBean(DefaultWebSecurityManager securityManager) {
//        MethodInvokingFactoryBean bean = new MethodInvokingFactoryBean();
//        bean.setStaticMethod("org.apache.shiro.SecurityUtils.setSecurityManager");
//        bean.setArguments(new Object[]{securityManager});
//        return bean;
//    }

    /**
     * 保证实现了Shiro内部lifecycle函数的bean执行
     */
//    @Bean
//    public LifecycleBeanPostProcessor lifecycleBeanPostProcessor() {
//        return new LifecycleBeanPostProcessor();
//    }

    /**
     * 启用shrio授权注解拦截方式，AOP式方法级权限检查
     */
//    @Bean
//    @DependsOn(value = "lifecycleBeanPostProcessor") //依赖其他bean的初始化
//    public DefaultAdvisorAutoProxyCreator defaultAdvisorAutoProxyCreator() {
//        return new DefaultAdvisorAutoProxyCreator();
//    }
//
//    @Bean
//    public AuthorizationAttributeSourceAdvisor authorizationAttributeSourceAdvisor(DefaultWebSecurityManager securityManager) {
//        AuthorizationAttributeSourceAdvisor authorizationAttributeSourceAdvisor =
//                new AuthorizationAttributeSourceAdvisor();
//        authorizationAttributeSourceAdvisor.setSecurityManager(securityManager);
//        return authorizationAttributeSourceAdvisor;
//    }
}
